home *** CD-ROM | disk | FTP | other *** search
/ NetNews Offline 2 / NetNews Offline Volume 2.iso / news / comp / lang / c++-part2 / 16873 < prev    next >
Encoding:
Text File  |  1996-08-05  |  3.6 KB  |  112 lines

  1. Newsgroups: comp.lang.c++
  2. Path: dmocc2.on.bell.ca!bc2cep!news
  3. From: g2david@sprynet.com (David Leung)
  4. Subject: Re: Friend vs. Member function for operator overload
  5. X-Nntp-Posting-Host: duncjm.on.bell.ca
  6. Message-ID: <Dpr5Ex.CC9@on.bell.ca>
  7. Sender: news@on.bell.ca (news admin)
  8. Reply-To: g2david@sprynet.com (David Leung)
  9. Organization: Bell Canada, Bell Sygma, SRCI
  10. X-Newsreader: IBM NewsReader/2 v1.02
  11. References: <4kj55n$mv2@homenet.hom.net>
  12. Date: Fri, 12 Apr 1996 13:56:57 GMT
  13.  
  14. In <4kj55n$mv2@homenet.hom.net>, dengel@hom.net (Daniel P. Engel III) writes:
  15. >Can anyone tell me the relative advantages and disadvantages of using
  16. >a friend function vs. a member function to overload an operator, such
  17. >as addition?  For example, suppose you have a Complex class (I'm not
  18. >interested in building a complex class--I'm just using this for an
  19. >example.):
  20. >
  21. >class Complex {
  22. >private:
  23. >    int real, imag;
  24. >.. . . 
  25. >};
  26. >
  27. >Now, you would want to be able to add complex numbers, like so:
  28. >
  29. >Complex a, b, c;
  30. >
  31. >a = (some complex number);
  32. >b = (some complex number);
  33. >c = a + b;
  34. >
  35. >Now, as far as I can tell, there are two general approaches to this.
  36. >One is the declare a friend function header in the class definition:
  37. >
  38. >friend Complex operator+( Complex& a, Complex& b) ;
  39. >
  40. >and then define that function something like:
  41. >
  42. >Complex operator+( Complex& const a, Complex& const b) {
  43. >    Complex temp;
  44. >    temp.real = a.real + b.real;
  45. >    temp.imag = a.imag + b.imag;
  46. >    return temp;
  47. >}
  48. >
  49. >The other way is to put the operator in the class definition itself:
  50. >
  51. >Complex operator+( Complex& const a) {
  52. >    Complex temp;
  53. >    temp.real = this->real + a.real;
  54. >    temp.imag = this->imag + a.imag;
  55. >    return temp;
  56. >}
  57. >
  58. >Can anyone tell me if one of these the "preferred" way of doing it?
  59. >And, what are the advantages and disadvantages of each?
  60. >
  61.  
  62.  
  63. I find an answer for you... 
  64.  
  65.  
  66. From Book "Black Belt C++: The Master Collection" 
  67.     Chapter "Special member functions and programming technique" 
  68.     by Bruce Eckel
  69.  
  70. Excerpt from this paper:
  71.  
  72. Member versus Friend Operators
  73.  
  74. When overloading operators, many people get confused about whether to use member functions or friend functions.
  75. There is a difference- the compiler can do conversion for both operands of a friend function,
  76. whereas it can only convert the right-hand argument of a member function. The left-hand argument of a member
  77. function must always be an object of the class type.
  78.  
  79. This means you can control the use of the operator by choosing a friend or member function. In the following
  80. example, you can only add apple, you can't add oranges to apples. On the other hand, operator-() is a friend
  81. function so it is reflectie, and since there is a way to convert from an orange to apple 
  82. (the conversion constructor in apple) you can subtract apples and oranges in any combination.
  83.  
  84. struct orange {};
  85.  
  86. struct apple {
  87.     void operator+(orange) {}
  88.     friend void operator-(apple,apple) {}
  89.     apple(orange) {} // make apple from orange
  90.     apple() //must create a default
  91. };
  92.  
  93. void main() {
  94.     apple a;
  95.     orange o;
  96.     a + o; // this works
  97.     // o + a; // this doesn't
  98.     a - a works;
  99.     a - 0
  100.     o - a 
  101.     o - o all works
  102. }
  103.  
  104. the last statement is a little surprising. You can even subtract an orange from an orange, even
  105. though there's no operator-() defined for orange! automatic type conversion is happening for both
  106. arguments. This is another situation that points out that automatic type conversion can 
  107. cause tricky things to happen.
  108.  
  109. Note: Structs are used here where normally the kind of information necessary to create
  110. an apple from an orange would be private. In the case, orange would have to grant the apple constructor
  111. friend status. This connects the two classes a little more closely and gives the reader a cue.
  112.